<template>
  <view class="ui-popover" :class="popover ? 'show' : 'hide'">
    <view
      :id="'popover-button-' + elId"
      class="ui-popover-button"
      :class="[ui]"
      :style="{ zIndex: index + zIndexConfig.popover }"
      @tap="popoverClick"
      @mouseleave="mouseleave"
      @mouseover="mouseover"
    >
      <slot></slot>
    </view>
    <view class="ui-popover-box" :style="BoxStyle">
      <view :id="'popover-content-' + elId" class="ui-popover-content-box" :style="contentStyle">
        <view
          class="ui-popover-content radius text-a"
          :class="bg"
          :style="{ zIndex: index + zIndexConfig.popover + 2 }"
        >
          <view v-if="tips" class="p-3 text-sm">{{ tips }}</view>
          <block v-else><slot name="content" /></block>
        </view>
        <view class="ui-popover-arrow" :class="bg" :style="arrowStyle"></view>
      </view>
    </view>
    <view
      v-if="(popover && tips == '' && time == 0) || mask"
      class="ui-popover-mask"
      :class="mask ? 'bg-mask-50' : ''"
      :style="{ zIndex: index + zIndexConfig.popover - 1 }"
      @tap="popover = false"
    ></view>
  </view>
</template>

<script>
import { guid } from '@/utils/helper'
import zIndexConfig from '@/sheep/config/zIndex.js'
import sheep from '@/sheep'

export default {
  name: 'SuPopover',
  props: {
    ui: {
      type: String,
      default: '',
    },
    tips: {
      type: String,
      default: '',
    },
    bg: {
      type: String,
      default: 'ui-BG',
    },
    mask: {
      type: Boolean,
      default: false,
    },
    show: {
      type: [Boolean, String],
      default: 'change',
    },
    hover: {
      type: Boolean,
      default: false,
    },
    index: {
      type: Number,
      default: 0,
    },
    time: {
      type: Number,
      default: 0,
    },
    bottom: {
      type: Boolean,
      default: false,
    },
    isChange: {
      type: Boolean,
      default: false,
    },
  },
  data() {
    return {
      elId: guid(),
      zIndexConfig,
      popover: false,
      BoxStyle: '',
      contentStyle: '',
      arrowStyle: '',
      button: {},
      content: {},
    }
  },
  watch: {
    popover(val) {
      this._computedQuery(sheep.$platform.device.windowWidth, sheep.$platform.device.windowHeight)
      if (val) {
        if (this.tips != '' || this.time > 0) {
          setTimeout(
            () => {
              this.popover = false
            },
            this.time == 0 ? 3000 : this.time
          )
        }
        this.sys_layer = this.sys_layer + 100
      } else {
        this.sys_layer = this.sys_layer - 100
      }
      this.$emit('update:show', val)
    },
    show(val) {
      this.popover = val
    },
  },
  mounted() {
    this.$nextTick(() => {
      this._computedQuery(sheep.$platform.device.windowWidth, sheep.$platform.device.windowHeight)
      // #ifdef H5
      uni.onWindowResize((res) => {
        this._computedQuery(res.size.windowWidth, res.size.windowHeight)
      })
      // #endif
    })
  },
  methods: {
    _onHide() {
      this.popover = false
    },
    _computedQuery(w, h) {
      uni
        .createSelectorQuery()
        .in(this)
        .select('#popover-button-' + this.elId)
        .boundingClientRect((button) => {
          if (button != null) {
            this.button = button
          } else {
            console.log('popover-button-' + this.elId + ' data error')
          }
        })
        .select('#popover-content-' + this.elId)
        .boundingClientRect((content) => {
          if (content != null) {
            this.content = content
            let button = this.button
            //contentStyle
            let contentStyle = ''
            let arrowStyle = ''
            this.BoxStyle = `width:${w}px; left:-${button.left}px;z-index: ${this.index + this.sys_layer + 102}`
            // 判断气泡在上面还是下面
            if (button.bottom < h / 2 || this.bottom) {
              // '下';
              contentStyle = contentStyle + `top:10px;`
              arrowStyle = arrowStyle + `top:${-5}px;`
            } else {
              // '上';
              contentStyle = contentStyle + `bottom:${button.height + 10}px;`
              arrowStyle = arrowStyle + `bottom:${-5}px;`
            }

            // 判断气泡箭头在左中右
            let btnCenter = button.right - button.width / 2
            let contentCenter = content.right - content.width / 2
            if ((btnCenter < w / 3 && content.width > btnCenter) || (content.width > w / 2 && btnCenter < w / 2)) {
              // '左';
              contentStyle = contentStyle + `left:10px;`
              arrowStyle = arrowStyle + `left:${btnCenter - 17}px;`
            } else if (
              (btnCenter > (w / 6) * 4 && content.width > w - btnCenter) ||
              (content.width > w / 2 && btnCenter > w / 2)
            ) {
              // '右';
              contentStyle = contentStyle + `right:10px;`
              arrowStyle = arrowStyle + `right:${w - btnCenter - 17}px;`
            } else {
              // '中';
              contentStyle = contentStyle + `left:${button.left - content.width / 2 + button.width / 2}px;`
              arrowStyle = arrowStyle + `left:0px;right:0px;margin:auto;`
            }

            this.arrowStyle = arrowStyle + `z-index:${this.index + this.sys_layer + 1};`
            this.contentStyle = contentStyle + `z-index:${this.index + this.sys_layer + 2};`
          } else {
            console.log('popover-content-' + this.elId + ' data error')
          }
        })
        .exec()
    },
    popoverClick() {
      if (this.isChange) {
        return false
      }
      if (this.tips == '') {
        this.popover = !this.popover
      } else {
        this.popover = true
      }
    },
    mouseover() {
      if (this.hover && (this.tips != '' || this.content.height != 0)) {
        this.popover = true
      }
    },
    mouseleave() {
      if (this.hover) {
        this.popover = false
      }
    },
  },
}
</script>

<style lang="scss">
.ui-popover {
  position: relative;

  .ui-popover-button {
    position: relative;
  }

  .ui-popover-box {
    position: absolute;

    .ui-popover-content-box {
      position: absolute;

      .ui-popover-content {
        position: relative;
      }

      .ui-popover-arrow {
        position: absolute;
        height: 15px;
        width: 15px;
        border-radius: 2px;
        transform: rotate(45deg);
      }

      &::after {
        content: '';
        width: 100%;
        height: 110%;
        position: absolute;
        background-color: #000000;
        top: 5%;
        left: 0;
        filter: blur(15px);
        opacity: 0.15;
      }
    }
  }

  .ui-popover-mask {
    position: fixed;
    width: 100%;
    height: 100%;
    top: 0;
    left: 0;
  }

  &.show {
    .ui-popover-button {
    }

    .ui-popover-content-box {
      opacity: 1;
      pointer-events: auto;
    }

    .ui-popover-arrow {
      display: block;
    }

    .ui-popover-mask {
      display: block;
    }
  }

  &.hide {
    .ui-popover-button {
    }

    .ui-popover-content-box {
      opacity: 0;
      pointer-events: none;
    }

    .ui-popover-arrow {
      display: none;
    }

    .ui-popover-mask {
      display: none;
    }
  }
}
</style>
